// ASCII folding implementation inspired by Lucene's ASCIIFoldingFilter.
// Converts non-ASCII Latin letters and various symbols to ASCII equivalents.
// This aims to be compatible with Lucene's mapping list used in ASCIIFoldingFilter.

use std::borrow::Cow;

pub fn fold_to_ascii_cow<'a>(input: Cow<'a, str>) -> Cow<'a, str> {
    // Cheap check if already ASCII
    if input.is_ascii() {
        return input;
    }

    Cow::Owned(fold_to_ascii(input.as_ref()))
}

pub fn fold_to_ascii(input: &str) -> String {
    let mut out = String::with_capacity(input.len());
    for ch in input.chars() {
        if ch.is_ascii() {
            out.push(ch);
            continue;
        }
        match fold_char(ch) {
            Some(repl) => out.push_str(repl),
            None => out.push(ch),
        }
    }
    out.shrink_to_fit();
    out
}

#[inline]
fn fold_char(c: char) -> Option<&'static str> {
    // Quick test
    if c < '\u{0080}' {
        return None;
    }

    // Main mapping translated from Lucene's ASCIIFoldingFilter
    let s = match c {
        // A/a
        '\u{00C0}' | '\u{00C1}' | '\u{00C2}' | '\u{00C3}' | '\u{00C4}' | '\u{00C5}'
        | '\u{0100}' | '\u{0102}' | '\u{0104}' | '\u{01CD}' | '\u{01DE}' | '\u{01E0}'
        | '\u{01FA}' | '\u{0200}' | '\u{0202}' | '\u{0226}' | '\u{023A}' | '\u{1D00}'
        | '\u{1E00}' | '\u{1EA0}' | '\u{1EA2}' | '\u{1EA4}' | '\u{1EA6}' | '\u{1EA8}'
        | '\u{1EAA}' | '\u{1EAC}' | '\u{1EAE}' | '\u{1EB0}' | '\u{1EB2}' | '\u{1EB4}'
        | '\u{1EB6}' | '\u{24B6}' | '\u{FF21}' => "A",
        '\u{00E0}' | '\u{00E1}' | '\u{00E2}' | '\u{00E3}' | '\u{00E4}' | '\u{00E5}'
        | '\u{0101}' | '\u{0103}' | '\u{0105}' | '\u{01CE}' | '\u{01DF}' | '\u{01E1}'
        | '\u{01FB}' | '\u{0201}' | '\u{0203}' | '\u{0227}' | '\u{0250}' | '\u{0259}'
        | '\u{025A}' | '\u{1D8F}' | '\u{1D95}' | '\u{1E01}' | '\u{1E9A}' | '\u{1EA1}'
        | '\u{1EA3}' | '\u{1EA5}' | '\u{1EA7}' | '\u{1EA9}' | '\u{1EAB}' | '\u{1EAD}'
        | '\u{1EAF}' | '\u{1EB1}' | '\u{1EB3}' | '\u{1EB5}' | '\u{1EB7}' | '\u{2090}'
        | '\u{2094}' | '\u{24D0}' | '\u{2C65}' | '\u{2C6F}' | '\u{FF41}' => "a",
        '\u{A732}' => "AA", // Ꜳ
        '\u{00C6}' | '\u{01E2}' | '\u{01FC}' | '\u{1D01}' => "AE",
        '\u{A734}' => "AO",
        '\u{A736}' => "AU",
        '\u{A738}' | '\u{A73A}' => "AV",
        '\u{A73C}' => "AY",
        '\u{249C}' => "(a)",
        '\u{A733}' => "aa",
        '\u{00E6}' | '\u{01E3}' | '\u{01FD}' | '\u{1D02}' => "ae",
        '\u{A735}' => "ao",
        '\u{A737}' => "au",
        '\u{A739}' | '\u{A73B}' => "av",
        '\u{A73D}' => "ay",

        // B/b
        '\u{0181}' | '\u{0182}' | '\u{0243}' | '\u{0299}' | '\u{1D03}' | '\u{1E02}'
        | '\u{1E04}' | '\u{1E06}' | '\u{24B7}' | '\u{FF22}' => "B",
        '\u{0180}' | '\u{0183}' | '\u{0253}' | '\u{1D6C}' | '\u{1D80}' | '\u{1E03}'
        | '\u{1E05}' | '\u{1E07}' | '\u{24D1}' | '\u{FF42}' => "b",
        '\u{249D}' => "(b)",

        // C/c
        '\u{00C7}' | '\u{0106}' | '\u{0108}' | '\u{010A}' | '\u{010C}' | '\u{0187}'
        | '\u{023B}' | '\u{0297}' | '\u{1D04}' | '\u{1E08}' | '\u{24B8}' | '\u{FF23}' => "C",
        '\u{00E7}' | '\u{0107}' | '\u{0109}' | '\u{010B}' | '\u{010D}' | '\u{0188}'
        | '\u{023C}' | '\u{0255}' | '\u{1E09}' | '\u{2184}' | '\u{24D2}' | '\u{A73E}'
        | '\u{A73F}' | '\u{FF43}' => "c",
        '\u{249E}' => "(c)",

        // D/d
        '\u{00D0}' | '\u{010E}' | '\u{0110}' | '\u{0189}' | '\u{018A}' | '\u{018B}'
        | '\u{1D05}' | '\u{1D06}' | '\u{1E0A}' | '\u{1E0C}' | '\u{1E0E}' | '\u{1E10}'
        | '\u{1E12}' | '\u{24B9}' | '\u{A779}' | '\u{FF24}' => "D",
        '\u{00F0}' | '\u{010F}' | '\u{0111}' | '\u{018C}' | '\u{0221}' | '\u{0256}'
        | '\u{0257}' | '\u{1D6D}' | '\u{1D81}' | '\u{1D91}' | '\u{1E0B}' | '\u{1E0D}'
        | '\u{1E0F}' | '\u{1E11}' | '\u{1E13}' | '\u{24D3}' | '\u{A77A}' | '\u{FF44}' => "d",
        '\u{01C4}' | '\u{01F1}' => "DZ",
        '\u{01C5}' | '\u{01F2}' => "Dz",
        '\u{249F}' => "(d)",
        '\u{0238}' => "db",
        '\u{01C6}' | '\u{01F3}' | '\u{02A3}' | '\u{02A5}' => "dz",

        // E/e
        '\u{00C8}' | '\u{00C9}' | '\u{00CA}' | '\u{00CB}' | '\u{0112}' | '\u{0114}'
        | '\u{0116}' | '\u{0118}' | '\u{011A}' | '\u{018E}' | '\u{0190}' | '\u{0204}'
        | '\u{0206}' | '\u{0228}' | '\u{0246}' | '\u{1D07}' | '\u{1E14}' | '\u{1E16}'
        | '\u{1E18}' | '\u{1E1A}' | '\u{1E1C}' | '\u{1EB8}' | '\u{1EBA}' | '\u{1EBC}'
        | '\u{1EBE}' | '\u{1EC0}' | '\u{1EC2}' | '\u{1EC4}' | '\u{1EC6}' | '\u{24BA}'
        | '\u{2C7B}' | '\u{FF25}' => "E",
        '\u{00E8}' | '\u{00E9}' | '\u{00EA}' | '\u{00EB}' | '\u{0113}' | '\u{0115}'
        | '\u{0117}' | '\u{0119}' | '\u{011B}' | '\u{01DD}' | '\u{0205}' | '\u{0207}'
        | '\u{0229}' | '\u{0247}' | '\u{0258}' | '\u{025B}' | '\u{025C}' | '\u{025D}'
        | '\u{025E}' | '\u{029A}' | '\u{1D08}' | '\u{1D92}' | '\u{1D93}' | '\u{1D94}'
        | '\u{1E15}' | '\u{1E17}' | '\u{1E19}' | '\u{1E1B}' | '\u{1E1D}' | '\u{1EB9}'
        | '\u{1EBB}' | '\u{1EBD}' | '\u{1EBF}' | '\u{1EC1}' | '\u{1EC3}' | '\u{1EC5}'
        | '\u{1EC7}' | '\u{2091}' | '\u{24D4}' | '\u{2C78}' | '\u{FF45}' => "e",
        '\u{24A0}' => "(e)",

        // F/f and ligatures
        '\u{0191}' | '\u{1E1E}' | '\u{24BB}' | '\u{A730}' | '\u{A77B}' | '\u{A7FB}'
        | '\u{FF26}' => "F",
        '\u{0192}' | '\u{1D6E}' | '\u{1D82}' | '\u{1E1F}' | '\u{1E9B}' | '\u{24D5}'
        | '\u{A77C}' | '\u{FF46}' => "f",
        '\u{24A1}' => "(f)",
        '\u{FB00}' => "ff",
        '\u{FB03}' => "ffi",
        '\u{FB04}' => "ffl",
        '\u{FB01}' => "fi",
        '\u{FB02}' => "fl",

        // G/g
        '\u{011C}' | '\u{011E}' | '\u{0120}' | '\u{0122}' | '\u{0193}' | '\u{01E4}'
        | '\u{01E6}' | '\u{01F4}' | '\u{0262}' | '\u{029B}' | '\u{1E20}' | '\u{24BC}'
        | '\u{A77D}' | '\u{A77E}' | '\u{FF27}' => "G",
        '\u{011D}' | '\u{011F}' | '\u{0121}' | '\u{0123}' | '\u{01E5}' | '\u{01E7}'
        | '\u{01F5}' | '\u{0260}' | '\u{0261}' | '\u{1D77}' | '\u{1D79}' | '\u{1D83}'
        | '\u{1E21}' | '\u{24D6}' | '\u{A77F}' | '\u{FF47}' => "g",
        '\u{24A2}' => "(g)",

        // H/h, HV
        '\u{0124}' | '\u{0126}' | '\u{021E}' | '\u{029C}' | '\u{1E22}' | '\u{1E24}'
        | '\u{1E26}' | '\u{1E28}' | '\u{1E2A}' | '\u{24BD}' | '\u{2C67}' | '\u{2C75}'
        | '\u{FF28}' => "H",
        '\u{0125}' | '\u{0127}' | '\u{021F}' | '\u{0265}' | '\u{0266}' | '\u{02AE}'
        | '\u{02AF}' | '\u{1E23}' | '\u{1E25}' | '\u{1E27}' | '\u{1E29}' | '\u{1E2B}'
        | '\u{1E96}' | '\u{24D7}' | '\u{2C68}' | '\u{2C76}' | '\u{FF48}' => "h",
        '\u{01F6}' => "HV",
        '\u{24A3}' => "(h)",
        '\u{0195}' => "hv",

        // I/i, IJ
        '\u{00CC}' | '\u{00CD}' | '\u{00CE}' | '\u{00CF}' | '\u{0128}' | '\u{012A}'
        | '\u{012C}' | '\u{012E}' | '\u{0130}' | '\u{0196}' | '\u{0197}' | '\u{01CF}'
        | '\u{0208}' | '\u{020A}' | '\u{026A}' | '\u{1D7B}' | '\u{1E2C}' | '\u{1E2E}'
        | '\u{1EC8}' | '\u{1ECA}' | '\u{24BE}' | '\u{A7FE}' | '\u{FF29}' => "I",
        '\u{00EC}' | '\u{00ED}' | '\u{00EE}' | '\u{00EF}' | '\u{0129}' | '\u{012B}'
        | '\u{012D}' | '\u{012F}' | '\u{0131}' | '\u{01D0}' | '\u{0209}' | '\u{020B}'
        | '\u{0268}' | '\u{1D09}' | '\u{1D62}' | '\u{1D7C}' | '\u{1D96}' | '\u{1E2D}'
        | '\u{1E2F}' | '\u{1EC9}' | '\u{1ECB}' | '\u{2071}' | '\u{24D8}' | '\u{FF49}' => "i",
        '\u{0132}' => "IJ",
        '\u{24A4}' => "(i)",
        '\u{0133}' => "ij",

        // J/j
        '\u{0134}' | '\u{0248}' | '\u{1D0A}' | '\u{24BF}' | '\u{FF2A}' => "J",
        '\u{0135}' | '\u{01F0}' | '\u{0237}' | '\u{0249}' | '\u{025F}' | '\u{0284}'
        | '\u{029D}' | '\u{24D9}' | '\u{2C7C}' | '\u{FF4A}' => "j",
        '\u{24A5}' => "(j)",

        // K/k
        '\u{0136}' | '\u{0198}' | '\u{01E8}' | '\u{1D0B}' | '\u{1E30}' | '\u{1E32}'
        | '\u{1E34}' | '\u{24C0}' | '\u{2C69}' | '\u{A740}' | '\u{A742}' | '\u{A744}'
        | '\u{FF2B}' => "K",
        '\u{0137}' | '\u{0199}' | '\u{01E9}' | '\u{029E}' | '\u{1D84}' | '\u{1E31}'
        | '\u{1E33}' | '\u{1E35}' | '\u{24DA}' | '\u{2C6A}' | '\u{A741}' | '\u{A743}'
        | '\u{A745}' | '\u{FF4B}' => "k",
        '\u{24A6}' => "(k)",

        // L/l, LJ/ll etc.
        '\u{0139}' | '\u{013B}' | '\u{013D}' | '\u{013F}' | '\u{0141}' | '\u{023D}'
        | '\u{029F}' | '\u{1D0C}' | '\u{1E36}' | '\u{1E38}' | '\u{1E3A}' | '\u{1E3C}'
        | '\u{24C1}' | '\u{2C60}' | '\u{2C62}' | '\u{A746}' | '\u{A748}' | '\u{A780}'
        | '\u{FF2C}' => "L",
        '\u{013A}' | '\u{013C}' | '\u{013E}' | '\u{0140}' | '\u{0142}' | '\u{019A}'
        | '\u{0234}' | '\u{026B}' | '\u{026C}' | '\u{026D}' | '\u{1D85}' | '\u{1E37}'
        | '\u{1E39}' | '\u{1E3B}' | '\u{1E3D}' | '\u{24DB}' | '\u{2C61}' | '\u{A747}'
        | '\u{A749}' | '\u{A781}' | '\u{FF4C}' => "l",
        '\u{01C7}' => "LJ",
        '\u{1EFA}' => "LL",
        '\u{01C8}' => "Lj",
        '\u{24A7}' => "(l)",
        '\u{01C9}' => "lj",
        '\u{1EFB}' => "ll",
        '\u{02AA}' => "ls",
        '\u{02AB}' => "lz",

        // M/m
        '\u{019C}' | '\u{1D0D}' | '\u{1E3E}' | '\u{1E40}' | '\u{1E42}' | '\u{24C2}'
        | '\u{2C6E}' | '\u{A7FD}' | '\u{A7FF}' | '\u{FF2D}' => "M",
        '\u{026F}' | '\u{0270}' | '\u{0271}' | '\u{1D6F}' | '\u{1D86}' | '\u{1E3F}'
        | '\u{1E41}' | '\u{1E43}' | '\u{24DC}' | '\u{FF4D}' => "m",
        '\u{24A8}' => "(m)",

        // N/n, NJ
        '\u{00D1}' | '\u{0143}' | '\u{0145}' | '\u{0147}' | '\u{014A}' | '\u{019D}'
        | '\u{01F8}' | '\u{0220}' | '\u{0274}' | '\u{1D0E}' | '\u{1E44}' | '\u{1E46}'
        | '\u{1E48}' | '\u{1E4A}' | '\u{24C3}' | '\u{FF2E}' => "N",
        '\u{00F1}' | '\u{0144}' | '\u{0146}' | '\u{0148}' | '\u{0149}' | '\u{014B}'
        | '\u{019E}' | '\u{01F9}' | '\u{0235}' | '\u{0272}' | '\u{0273}' | '\u{1D70}'
        | '\u{1D87}' | '\u{1E45}' | '\u{1E47}' | '\u{1E49}' | '\u{1E4B}' | '\u{207F}'
        | '\u{24DD}' | '\u{FF4E}' => "n",
        '\u{01CA}' => "NJ",
        '\u{01CB}' => "Nj",
        '\u{24A9}' => "(n)",
        '\u{01CC}' => "nj",

        // O/o, OE/OO/OU
        '\u{00D2}' | '\u{00D3}' | '\u{00D4}' | '\u{00D5}' | '\u{00D6}' | '\u{00D8}'
        | '\u{014C}' | '\u{014E}' | '\u{0150}' | '\u{0186}' | '\u{019F}' | '\u{01A0}'
        | '\u{01D1}' | '\u{01EA}' | '\u{01EC}' | '\u{01FE}' | '\u{020C}' | '\u{020E}'
        | '\u{022A}' | '\u{022C}' | '\u{022E}' | '\u{0230}' | '\u{1D0F}' | '\u{1D10}'
        | '\u{1E4C}' | '\u{1E4E}' | '\u{1E50}' | '\u{1E52}' | '\u{1ECC}' | '\u{1ECE}'
        | '\u{1ED0}' | '\u{1ED2}' | '\u{1ED4}' | '\u{1ED6}' | '\u{1ED8}' | '\u{1EDA}'
        | '\u{1EDC}' | '\u{1EDE}' | '\u{1EE0}' | '\u{1EE2}' | '\u{24C4}' | '\u{A74A}'
        | '\u{A74C}' | '\u{FF2F}' => "O",
        '\u{00F2}' | '\u{00F3}' | '\u{00F4}' | '\u{00F5}' | '\u{00F6}' | '\u{00F8}'
        | '\u{014D}' | '\u{014F}' | '\u{0151}' | '\u{01A1}' | '\u{01D2}' | '\u{01EB}'
        | '\u{01ED}' | '\u{01FF}' | '\u{020D}' | '\u{020F}' | '\u{022B}' | '\u{022D}'
        | '\u{022F}' | '\u{0231}' | '\u{0254}' | '\u{0275}' | '\u{1D16}' | '\u{1D17}'
        | '\u{1D97}' | '\u{1E4D}' | '\u{1E4F}' | '\u{1E51}' | '\u{1E53}' | '\u{1ECD}'
        | '\u{1ECF}' | '\u{1ED1}' | '\u{1ED3}' | '\u{1ED5}' | '\u{1ED7}' | '\u{1ED9}'
        | '\u{1EDB}' | '\u{1EDD}' | '\u{1EDF}' | '\u{1EE1}' | '\u{1EE3}' | '\u{2092}'
        | '\u{24DE}' | '\u{2C7A}' | '\u{A74B}' | '\u{A74D}' | '\u{FF4F}' => "o",
        '\u{0152}' | '\u{0276}' => "OE",
        '\u{A74E}' => "OO",
        '\u{0222}' | '\u{1D15}' => "OU",
        '\u{24AA}' => "(o)",
        '\u{0153}' | '\u{1D14}' => "oe",
        '\u{A74F}' => "oo",
        '\u{0223}' => "ou",

        // P/p
        '\u{01A4}' | '\u{1D18}' | '\u{1E54}' | '\u{1E56}' | '\u{24C5}' | '\u{2C63}'
        | '\u{A750}' | '\u{A752}' | '\u{A754}' | '\u{FF30}' => "P",
        '\u{01A5}' | '\u{1D71}' | '\u{1D7D}' | '\u{1D88}' | '\u{1E55}' | '\u{1E57}'
        | '\u{24DF}' | '\u{A751}' | '\u{A753}' | '\u{A755}' | '\u{A7FC}' | '\u{FF50}' => "p",
        '\u{24AB}' => "(p)",

        // Q/q
        '\u{024A}' | '\u{24C6}' | '\u{A756}' | '\u{A758}' | '\u{FF31}' => "Q",
        '\u{0138}' | '\u{024B}' | '\u{02A0}' | '\u{24E0}' | '\u{A757}' | '\u{A759}'
        | '\u{FF51}' => "q",
        '\u{24AC}' => "(q)",
        '\u{0239}' => "qp",

        // R/r
        '\u{0154}' | '\u{0156}' | '\u{0158}' | '\u{0210}' | '\u{0212}' | '\u{024C}'
        | '\u{0280}' | '\u{0281}' | '\u{1D19}' | '\u{1D1A}' | '\u{1E58}' | '\u{1E5A}'
        | '\u{1E5C}' | '\u{1E5E}' | '\u{24C7}' | '\u{2C64}' | '\u{A75A}' | '\u{A782}'
        | '\u{FF32}' => "R",
        '\u{0155}' | '\u{0157}' | '\u{0159}' | '\u{0211}' | '\u{0213}' | '\u{024D}'
        | '\u{027C}' | '\u{027D}' | '\u{027E}' | '\u{027F}' | '\u{1D63}' | '\u{1D72}'
        | '\u{1D73}' | '\u{1D89}' | '\u{1E59}' | '\u{1E5B}' | '\u{1E5D}' | '\u{1E5F}'
        | '\u{24E1}' | '\u{A75B}' | '\u{A783}' | '\u{FF52}' => "r",
        '\u{24AD}' => "(r)",

        // S/s and ß/ẞ and st
        '\u{015A}' | '\u{015C}' | '\u{015E}' | '\u{0160}' | '\u{0218}' | '\u{1E60}'
        | '\u{1E62}' | '\u{1E64}' | '\u{1E66}' | '\u{1E68}' | '\u{24C8}' | '\u{A731}'
        | '\u{A785}' | '\u{FF33}' => "S",
        '\u{015B}' | '\u{015D}' | '\u{015F}' | '\u{0161}' | '\u{017F}' | '\u{0219}'
        | '\u{023F}' | '\u{0282}' | '\u{1D74}' | '\u{1D8A}' | '\u{1E61}' | '\u{1E63}'
        | '\u{1E65}' | '\u{1E67}' | '\u{1E69}' | '\u{1E9C}' | '\u{1E9D}' | '\u{24E2}'
        | '\u{A784}' | '\u{FF53}' => "s",
        '\u{1E9E}' => "SS",
        '\u{24AE}' => "(s)",
        '\u{00DF}' => "ss",
        '\u{FB06}' => "st",

        // T/t, TH/th, TZ
        '\u{0162}' | '\u{0164}' | '\u{0166}' | '\u{01AC}' | '\u{01AE}' | '\u{021A}'
        | '\u{023E}' | '\u{1D1B}' | '\u{1E6A}' | '\u{1E6C}' | '\u{1E6E}' | '\u{1E70}'
        | '\u{24C9}' | '\u{A786}' | '\u{FF34}' => "T",
        '\u{0163}' | '\u{0165}' | '\u{0167}' | '\u{01AB}' | '\u{01AD}' | '\u{021B}'
        | '\u{0236}' | '\u{0287}' | '\u{0288}' | '\u{1D75}' | '\u{1E6B}' | '\u{1E6D}'
        | '\u{1E6F}' | '\u{1E71}' | '\u{1E97}' | '\u{24E3}' | '\u{2C66}' | '\u{FF54}' => "t",
        '\u{00DE}' | '\u{A766}' => "TH",
        '\u{A728}' => "TZ",
        '\u{24AF}' => "(t)",
        '\u{02A8}' => "tc",
        '\u{00FE}' | '\u{1D7A}' | '\u{A767}' => "th",
        '\u{02A6}' => "ts",
        '\u{A729}' => "tz",

        // U/u
        '\u{00D9}' | '\u{00DA}' | '\u{00DB}' | '\u{00DC}' | '\u{0168}' | '\u{016A}'
        | '\u{016C}' | '\u{016E}' | '\u{0170}' | '\u{0172}' | '\u{01AF}' | '\u{01D3}'
        | '\u{01D5}' | '\u{01D7}' | '\u{01D9}' | '\u{01DB}' | '\u{0214}' | '\u{0216}'
        | '\u{0244}' | '\u{1D1C}' | '\u{1D7E}' | '\u{1E72}' | '\u{1E74}' | '\u{1E76}'
        | '\u{1E78}' | '\u{1E7A}' | '\u{1EE4}' | '\u{1EE6}' | '\u{1EE8}' | '\u{1EEA}'
        | '\u{1EEC}' | '\u{1EEE}' | '\u{1EF0}' | '\u{24CA}' | '\u{FF35}' => "U",
        '\u{00F9}' | '\u{00FA}' | '\u{00FB}' | '\u{00FC}' | '\u{0169}' | '\u{016B}'
        | '\u{016D}' | '\u{016F}' | '\u{0171}' | '\u{0173}' | '\u{01B0}' | '\u{01D4}'
        | '\u{01D6}' | '\u{01D8}' | '\u{01DA}' | '\u{01DC}' | '\u{0215}' | '\u{0217}'
        | '\u{0289}' | '\u{1D64}' | '\u{1D99}' | '\u{1E73}' | '\u{1E75}' | '\u{1E77}'
        | '\u{1E79}' | '\u{1E7B}' | '\u{1EE5}' | '\u{1EE7}' | '\u{1EE9}' | '\u{1EEB}'
        | '\u{1EED}' | '\u{1EEF}' | '\u{1EF1}' | '\u{24E4}' | '\u{FF55}' => "u",
        '\u{24B0}' => "(u)",
        '\u{1D6B}' => "ue",

        // V/v
        '\u{01B2}' | '\u{0245}' | '\u{1D20}' | '\u{1E7C}' | '\u{1E7E}' | '\u{1EFC}'
        | '\u{24CB}' | '\u{A75E}' | '\u{A768}' | '\u{FF36}' => "V",
        '\u{028B}' | '\u{028C}' | '\u{1D65}' | '\u{1D8C}' | '\u{1E7D}' | '\u{1E7F}'
        | '\u{24E5}' | '\u{2C71}' | '\u{2C74}' | '\u{A75F}' | '\u{FF56}' => "v",
        '\u{A760}' => "VY",
        '\u{24B1}' => "(v)",
        '\u{A761}' => "vy",

        // W/w
        '\u{0174}' | '\u{01F7}' | '\u{1D21}' | '\u{1E80}' | '\u{1E82}' | '\u{1E84}'
        | '\u{1E86}' | '\u{1E88}' | '\u{24CC}' | '\u{2C72}' | '\u{FF37}' => "W",
        '\u{0175}' | '\u{01BF}' | '\u{028D}' | '\u{1E81}' | '\u{1E83}' | '\u{1E85}'
        | '\u{1E87}' | '\u{1E89}' | '\u{1E98}' | '\u{24E6}' | '\u{2C73}' | '\u{FF57}' => "w",
        '\u{24B2}' => "(w)",

        // X/x
        '\u{1E8A}' | '\u{1E8C}' | '\u{24CD}' | '\u{FF38}' => "X",
        '\u{1D8D}' | '\u{1E8B}' | '\u{1E8D}' | '\u{2093}' | '\u{24E7}' | '\u{FF58}' => "x",
        '\u{24B3}' => "(x)",

        // Y/y
        '\u{00DD}' | '\u{0176}' | '\u{0178}' | '\u{01B3}' | '\u{0232}' | '\u{024E}'
        | '\u{028F}' | '\u{1E8E}' | '\u{1EF2}' | '\u{1EF4}' | '\u{1EF6}' | '\u{1EF8}'
        | '\u{1EFE}' | '\u{24CE}' | '\u{FF39}' => "Y",
        '\u{00FD}' | '\u{00FF}' | '\u{0177}' | '\u{01B4}' | '\u{0233}' | '\u{024F}'
        | '\u{028E}' | '\u{1E8F}' | '\u{1E99}' | '\u{1EF3}' | '\u{1EF5}' | '\u{1EF7}'
        | '\u{1EF9}' | '\u{1EFF}' | '\u{24E8}' | '\u{FF59}' => "y",
        '\u{24B4}' => "(y)",

        // Z/z
        '\u{0179}' | '\u{017B}' | '\u{017D}' | '\u{01B5}' | '\u{021C}' | '\u{0224}'
        | '\u{1D22}' | '\u{1E90}' | '\u{1E92}' | '\u{1E94}' | '\u{24CF}' | '\u{2C6B}'
        | '\u{A762}' | '\u{FF3A}' => "Z",
        '\u{017A}' | '\u{017C}' | '\u{017E}' | '\u{01B6}' | '\u{021D}' | '\u{0225}'
        | '\u{0240}' | '\u{0290}' | '\u{0291}' | '\u{1D76}' | '\u{1D8E}' | '\u{1E91}'
        | '\u{1E93}' | '\u{1E95}' | '\u{24E9}' | '\u{2C6C}' | '\u{A763}' | '\u{FF5A}' => "z",
        '\u{24B5}' => "(z)",

        // Digits and circled/parenthesized forms
        '\u{2070}' | '\u{2080}' | '\u{24EA}' | '\u{24FF}' | '\u{FF10}' => "0",
        '\u{00B9}' | '\u{2081}' | '\u{2460}' | '\u{24F5}' | '\u{2776}' | '\u{2780}'
        | '\u{278A}' | '\u{FF11}' => "1",
        '\u{2488}' => "1.",
        '\u{2474}' => "(1)",
        '\u{00B2}' | '\u{2082}' | '\u{2461}' | '\u{24F6}' | '\u{2777}' | '\u{2781}'
        | '\u{278B}' | '\u{FF12}' => "2",
        '\u{2489}' => "2.",
        '\u{2475}' => "(2)",
        '\u{00B3}' | '\u{2083}' | '\u{2462}' | '\u{24F7}' | '\u{2778}' | '\u{2782}'
        | '\u{278C}' | '\u{FF13}' => "3",
        '\u{248A}' => "3.",
        '\u{2476}' => "(3)",
        '\u{2074}' | '\u{2084}' | '\u{2463}' | '\u{24F8}' | '\u{2779}' | '\u{2783}'
        | '\u{278D}' | '\u{FF14}' => "4",
        '\u{248B}' => "4.",
        '\u{2477}' => "(4)",
        '\u{2075}' | '\u{2085}' | '\u{2464}' | '\u{24F9}' | '\u{277A}' | '\u{2784}'
        | '\u{278E}' | '\u{FF15}' => "5",
        '\u{248C}' => "5.",
        '\u{2478}' => "(5)",
        '\u{2076}' | '\u{2086}' | '\u{2465}' | '\u{24FA}' | '\u{277B}' | '\u{2785}'
        | '\u{278F}' | '\u{FF16}' => "6",
        '\u{248D}' => "6.",
        '\u{2479}' => "(6)",
        '\u{2077}' | '\u{2087}' | '\u{2466}' | '\u{24FB}' | '\u{277C}' | '\u{2786}'
        | '\u{2790}' | '\u{FF17}' => "7",
        '\u{248E}' => "7.",
        '\u{247A}' => "(7)",
        '\u{2078}' | '\u{2088}' | '\u{2467}' | '\u{24FC}' | '\u{277D}' | '\u{2787}'
        | '\u{2791}' | '\u{FF18}' => "8",
        '\u{248F}' => "8.",
        '\u{247B}' => "(8)",
        '\u{2079}' | '\u{2089}' | '\u{2468}' | '\u{24FD}' | '\u{277E}' | '\u{2788}'
        | '\u{2792}' | '\u{FF19}' => "9",
        '\u{2490}' => "9.",
        '\u{247C}' => "(9)",
        '\u{2469}' | '\u{24FE}' | '\u{277F}' | '\u{2789}' | '\u{2793}' => "10",
        '\u{2491}' => "10.",
        '\u{247D}' => "(10)",
        '\u{246A}' | '\u{24EB}' => "11",
        '\u{2492}' => "11.",
        '\u{247E}' => "(11)",
        '\u{246B}' | '\u{24EC}' => "12",
        '\u{2493}' => "12.",
        '\u{247F}' => "(12)",
        '\u{246C}' | '\u{24ED}' => "13",
        '\u{2494}' => "13.",
        '\u{2480}' => "(13)",
        '\u{246D}' | '\u{24EE}' => "14",
        '\u{2495}' => "14.",
        '\u{2481}' => "(14)",
        '\u{246E}' | '\u{24EF}' => "15",
        '\u{2496}' => "15.",
        '\u{2482}' => "(15)",
        '\u{246F}' | '\u{24F0}' => "16",
        '\u{2497}' => "16.",
        '\u{2483}' => "(16)",
        '\u{2470}' | '\u{24F1}' => "17",
        '\u{2498}' => "17.",
        '\u{2484}' => "(17)",
        '\u{2471}' | '\u{24F2}' => "18",
        '\u{2499}' => "18.",
        '\u{2485}' => "(18)",
        '\u{2472}' | '\u{24F3}' => "19",
        '\u{249A}' => "19.",
        '\u{2486}' => "(19)",
        '\u{2473}' | '\u{24F4}' => "20",
        '\u{249B}' => "20.",
        '\u{2487}' => "(20)",

        // Quotes/dashes and punctuation
        '\u{00AB}' | '\u{00BB}' | '\u{201C}' | '\u{201D}' | '\u{201E}' | '\u{2033}'
        | '\u{2036}' | '\u{275D}' | '\u{275E}' | '\u{276E}' | '\u{276F}' | '\u{FF02}' => "\"",
        '\u{2018}' | '\u{2019}' | '\u{201A}' | '\u{201B}' | '\u{2032}' | '\u{2035}'
        | '\u{2039}' | '\u{203A}' | '\u{275B}' | '\u{275C}' | '\u{FF07}' => "'",
        '\u{2010}' | '\u{2011}' | '\u{2012}' | '\u{2013}' | '\u{2014}' | '\u{207B}'
        | '\u{208B}' | '\u{FF0D}' => "-",
        '\u{2045}' | '\u{2772}' | '\u{FF3B}' => "[",
        '\u{2046}' | '\u{2773}' | '\u{FF3D}' => "]",
        '\u{207D}' | '\u{208D}' | '\u{2768}' | '\u{276A}' | '\u{FF08}' => "(",
        '\u{2E28}' => "((",
        '\u{207E}' | '\u{208E}' | '\u{2769}' | '\u{276B}' | '\u{FF09}' => ")",
        '\u{2E29}' => "))",
        '\u{276C}' | '\u{2770}' | '\u{FF1C}' => "<",
        '\u{276D}' | '\u{2771}' | '\u{FF1E}' => ">",
        '\u{2774}' | '\u{FF5B}' => "{",
        '\u{2775}' | '\u{FF5D}' => "}",
        '\u{207A}' | '\u{208A}' | '\u{FF0B}' => "+",
        '\u{207C}' | '\u{208C}' | '\u{FF1D}' => "=",
        '\u{FF01}' => "!",
        '\u{203C}' => "!!",
        '\u{2049}' => "!?",
        '\u{FF03}' => "#",
        '\u{FF04}' => "$",
        '\u{2052}' | '\u{FF05}' => "%",
        '\u{FF06}' => "&",
        '\u{204E}' | '\u{FF0A}' => "*",
        '\u{FF0C}' => ",",
        '\u{FF0E}' => ".",
        '\u{2044}' | '\u{FF0F}' => "/",
        '\u{FF1A}' => ":",
        '\u{204F}' | '\u{FF1B}' => ";",
        '\u{FF1F}' => "?",
        '\u{2047}' => "??",
        '\u{2048}' => "?!",
        '\u{FF20}' => "@",
        '\u{FF3C}' => "\\",
        '\u{2038}' | '\u{FF3E}' => "^",
        '\u{FF3F}' => "_",
        '\u{2053}' | '\u{FF5E}' => "~",

        _ => return None,
    };
    Some(s)
}

#[cfg(test)]
mod tests {
    use super::fold_to_ascii;

    #[test]
    fn basic_examples() {
        assert_eq!(
            fold_to_ascii("ação café jalapeño Über"),
            "acao cafe jalapeno Uber"
        );
        assert_eq!(fold_to_ascii("Æsop and Œuvre"), "AEsop and OEuvre");
        assert_eq!(fold_to_ascii("straße"), "strasse");
        assert_eq!(fold_to_ascii("Łódź"), "Lodz");
        assert_eq!(
            fold_to_ascii("“quote” — test １②⒊"),
            "\"quote\" - test 123."
        );

        // japanese characters are unchanged
        assert_eq!(
            fold_to_ascii("日本語のテキストです。Qdrantのコードで単体テストで使用されています。"),
            "日本語のテキストです。Qdrantのコードで単体テストで使用されています。"
        );
    }
}
